<template>
  <div style="display: none">socket is hidden run</div>
</template>

<script>
import { mapGetters } from 'vuex'

export default {
  name: 'WebSocket',
  props: {
    // socket地址
    url: String,
    beatInterval: {
      type: Number,
      default: 10000
    }
  },
  computed: {
    ...mapGetters([
      'userId'
    ])
  },
  data() {
    return {
      fullUrl: '',
      websocket: null,
      timer: null
    }
  },
  watch: {

    url: {
      handler() {
        // 重新初始化
        this.initSocket()
      }
    }
  },

  mounted() {
    // 初始化
    this.initSocket()
  },
  destroyed() {
    console.log('+++++++++++++clear websocket：', this.fullUrl)
    // 销毁资源
    this.clear()
  },
  methods: {

    // 初始化接口
    initSocket() {
      // 清理
      this.clear()

      // 接口配置
      const api = process.env.VUE_APP_BASE_API

      // 同域代理
      if (api === null || api === '') {
        this.fullUrl = `${location.protocol === 'https:' ? 'wss' : 'ws'}://${location.host}${this.url}`
      } else {
        // 同接口替换
        this.fullUrl = api.replace('https://', 'wss://').replace('http://', 'ws://')
        this.fullUrl = `${this.fullUrl}${this.url}`
      }

      // 连接socket
      this.connect()
    },

    // 定时发送心跳
    beat() {
      // 清理定时器
      if (this.timer != null) {
        clearInterval(this.timer)
      }
      // 10秒联系一次
      this.timer = setInterval(() => {
        // 发送消息
        this.ping()
      }, this.beatInterval)

      // 首次触发
      this.ping()
    },

    // 发送消息保持连接
    ping() {
      if (this.websocket.readyState === 1) {
        // 首次触发
        this.websocket.send('ping')
      } else {
        // 只要错误就重新连接
        this.connect()
      }
    },

    // 进行连接
    connect() {
      console.log('++++connect', this.fullUrl)
      this.websocket = new WebSocket(this.fullUrl)
      this.websocket.onopen = this.onOpen
      this.websocket.onerror = this.onError
      this.websocket.onclose = this.onClose
      this.websocket.onmessage = this.onMessage
    },
    onOpen() {
      // 维持心跳
      this.beat()
    },
    onError(e) {
      console.log('socket error', e)
    },
    onClose(e) {
      console.log('socket error', e)
    },
    // 收到消息
    onMessage(e) {
      const data = e.data
      console.log('receive', data)
      // 收到消息回调
      this.$emit('receive', data)
    },
    // 销毁资源
    clear() {
      // 断开上一个连接
      if (this.websocket != null && this.websocket.readyState === 1) {
        this.websocket.close()
      }
      // 取消任务
      if (this.timer != null) {
        clearInterval(this.timer)
      }
    }
  }
}
</script>
